package com.flow.plugins;

import com.apache.api.manager.ProxyManager;
import com.apache.api.vo.ParamsVo;
import com.apache.api.vo.ResultEntity;
import com.apache.cache.util.Validator;
import com.apache.exception.BusinessException;
import com.apache.ius.plugin.CustomMethodPlugin;
import com.apache.ius.plugin.IusPluginUtil;
import com.apache.tools.DataMap;
import com.apache.tools.DateUtils;
import com.apache.tools.StrUtil;
import net.sf.json.JSONArray;
import net.sf.json.JSONObject;
import org.apache.log4j.Logger;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * 审核插件：完成当前审核表audit的审核操作，并且根据审核规则去初始化审核数据
 */
@SuppressWarnings("serial")
public class FlowNextPluginImpl implements CustomMethodPlugin {

    protected Logger log = Logger.getLogger(getClass());

    public Object doInvoke(Map<String, Object> param) {
        beforeInvoke(param);
        return null;
    }

    public Object beforeInvoke(Map<String, Object> param) {
        String auditsId = String.valueOf(param.get("auditsId"));
        String auditFlag = Validator.getDefaultStr(String.valueOf(param.get("auditFlag")), "T");
        String auditOpinion = String.valueOf(param.get("auditOpinion"));
        String auditsStatus = "91";
        if("F".equals(auditFlag)){
            auditsStatus="90";
        }
        String objColName = "";
        if (Validator.isNull(auditsId)) {
            throw new BusinessException(
                    "auditsId参数不能为空！请注意不是auditId而是auditsId！强调三遍audits，不是audit！audits，不是audit！audits，不是audit！");
        }

//        log.info("【开始执行审核任务】 - > auditsId="+auditsId+",auditFlag="+auditFlag+",auditOpinion="+auditOpinion);



        //更新audit表
        ResultEntity upResult = updateAudit(auditsId, auditsStatus, auditOpinion, param);
        if (!upResult.getResult().equals("T")) {
            throw new BusinessException("执行失败！");
        }

        String searchObjName = "s_sysAudit";
        Map<String, Object> whereMap = new HashMap<String, Object>();
        whereMap.put("sysAudit.w_auditsId", auditsId);
        ResultEntity auditResult = (ResultEntity) IusPluginUtil.getInstance().select("plateform","obj",searchObjName,whereMap);
        DataMap auditInfoDataMap = (DataMap) auditResult.getEntity();


        //根据当前nodeCode去找下一节点的值并且insert到audit中
        Map<String, Object> whereMap_auditRule = new HashMap<String, Object>();
        whereMap_auditRule.put("sysAuditRule.w_taskNo",String.valueOf(auditInfoDataMap.get("taskNo")));
        ResultEntity dymicSqlParamResult = (ResultEntity) IusPluginUtil.getInstance().select("plateform","list","s_sysAuditRule",whereMap_auditRule);
        List<DataMap> firstNodeList = (List<DataMap>) dymicSqlParamResult.getEntity();
        String nextNodeCode="";
        for (DataMap node:firstNodeList) {
            String nodeType="";
            nodeType = String.valueOf(node.get("nodeType"));
            String nodeConfig = String.valueOf(node.get("nodeConfig"));
            JSONObject jObject = JSONObject.fromObject(nodeConfig);
            JSONArray jsonArray = (JSONArray)jObject.get("nexts");
            if(jsonArray.size()>0){
                for(int i=0;i<jsonArray.size();i++){
                    JSONObject job = jsonArray.getJSONObject(i);  // 遍历 jsonarray 数组，把每一个对象转成 json 对象
                    nextNodeCode = String.valueOf(job.get("code"));
                    DataMap nextTaskNodeInfo = getNodeByCode(param,nextNodeCode);
                    if(nextTaskNodeInfo!=null){
//                        System.out.println("======================="+nextTaskNodeInfo.get("taskName"));
                        //            //如果是end节点，则不插入
                        if(!"end".equals(nextTaskNodeInfo.get("nodeType"))){
                            initAudit(nextTaskNodeInfo);
                        }else{
                            log.info("【已到结束节点】流程结束！！");
                        }
                    }

                }
            }

        }
















        //换成跨数据源的写法
//        String searchObjName = "s_sysAudit";
//        Map<String, Object> whereMap = new HashMap<String, Object>();
//        whereMap.put("sysAudit.w_auditsId", auditsId);
//        ResultEntity auditResult = (ResultEntity) IusPluginUtil.getInstance().select("plateform","obj",searchObjName,whereMap);
//        DataMap auditInfoDataMap = (DataMap) auditResult.getEntity();
//        if ("T".equals(auditFlag)) {
//            auditsStatus = "91";
//            //如果设定了其他表的待修改字段，需要封装ius里必要的参数
//            objColName = String.valueOf(auditInfoDataMap.get("colNameY"));//trpPro.proStatus=11,trpPro.auditStatus=11
//        } else {
//            auditsStatus = "90";
//            //如果设定了其他表的待修改字段，需要封装ius里必要的参数
//            objColName = String.valueOf(auditInfoDataMap.get("colNameN"));//trpPro.proStatus=11,trpPro.auditStatus=11
//        }

        //封装待修改的参数。2017-8-7 add
//        if (Validator.isNotNull(objColName)) {
//            String[] ColNameArray = objColName.split(",");
//            for (String str : ColNameArray) {
//                String key = str.split("=")[0];
//                String value = str.split("=")[1];
//                if (value.contains("[") && value.contains("]")) {
//                    value = value.replace("[", "");
//                    value = value.replace("]", "");
//                    value = String.valueOf(param.get(value));
//                }
//
//                param.put(key, value);
//            }
//        }

//        String nextUser = "";
//        if (auditsStatus.equals("90")) {
//            nextUser = String.valueOf(auditInfoDataMap.get("lastUser"));
//        } else {
//            nextUser = String.valueOf(auditInfoDataMap.get("nextUser"));
//        }
//        log.info("【查找是否有下级审核任务】 - > auditsStatus="+auditsStatus+",nextTaskNo="+nextUser);
        //则根据nextUser指向的节点编号去查询sysAuditRule的这条数据。
        //nextUser如果为00，则代表该节点为最后节点，流程到此结束，不需要去查询sysAuditRule表
//        if (!nextUser.equals("00")) {
////            DataMap sysAuditRule = getAuditRuleByTaskNo(iusProxyManager, nextUser);
//            //通过下一审核节点查询规则
//            String searchObjName_sysAuditRule = "s_sysAuditRule";
//            //换成跨数据源的写法
//            Map<String, Object> whereMap_sysAuditRule = new HashMap<String, Object>();
//            whereMap_sysAuditRule.put("sysAuditRule.w_auditType", String.valueOf(auditInfoDataMap.get("auditType")));
//            whereMap_sysAuditRule.put("sysAuditRule.w_taskNo", nextUser);
//            ResultEntity dymicSqlParamResult = (ResultEntity) IusPluginUtil.getInstance().select("plateform","obj",searchObjName_sysAuditRule,whereMap_sysAuditRule);
//            DataMap sysAuditRule =  (DataMap) dymicSqlParamResult.getEntity();
//
//
//            String nextNode = String.valueOf(sysAuditRule.get("next"));
//            String nodeConfig = String.valueOf(sysAuditRule.get("nodeConfig"));
//            JSONObject jObject = JSONObject.fromObject(nodeConfig);
//            String nodeType = String.valueOf(jObject.get("type"));
//            JSONArray jsonArray = (JSONArray)jObject.get("nexts");
//            if(!"end".equals(nodeType)){
//                if(jsonArray.size()>0){
//                    for(int i=0;i<jsonArray.size();i++){
//                        JSONObject job = jsonArray.getJSONObject(i);  // 遍历 jsonarray 数组，把每一个对象转成 json 对象
//                        if("judge".equals(nodeType)) {
//                            String rule = String.valueOf(job.get("rule"));
//                            String arg1 = rule.split("==")[0];
//                            String arg2 = rule.split("==")[1];
//                            if(arg2.equals(param.get(arg1))){
//                                nextNode = String.valueOf(job.get("code"));
//                                //如果是判断节点，则还需要查询一下next节点。
//                                String searchObjName_judge_next = "s_sysAuditRule";
//                                Map<String, Object> whereMap_judge_next = new HashMap<String, Object>();
//                                whereMap_judge_next.put("sysAuditRule.w_taskNo", nextNode);
//                                ResultEntity judgeNextResult = (ResultEntity) IusPluginUtil.getInstance().select("plateform","obj",searchObjName_judge_next,whereMap_judge_next);
//                                DataMap judgeNextMap =  (DataMap) judgeNextResult.getEntity();
//                                sysAuditRule = judgeNextMap;
//                                break;
//                            }
//
//
//                        }else if ("task".equals(nodeType)){
//                            nextNode = String.valueOf(job.get("code"));
//                        }
//                    }
//                }
//            }else{
//                log.info("【查找到无下级审核任务】流程结束！！");
//
//            }
//
//
//            //封装新的audit数据并且插入到audit表中。
//            String proId = String.valueOf(auditInfoDataMap.get("proId"));
//            String proName = String.valueOf(auditInfoDataMap.get("proName"));
//            if (Validator.isNull(proId)) {
//                throw new BusinessException("proId传递丢失！请检查！");
//            }
//
//            sysAuditRule.put("pro_id", proId);
//            if(Validator.isNotNull(proName)){
//                proName = proName+"-"+sysAuditRule.get("taskName");
//            }
//            sysAuditRule.put("pro_name", proName);
//
//            //如果是end节点，则不插入
//            if(!"end".equals(sysAuditRule.get("nodeType"))){
//                ResultEntity result = insertAudit(sysAuditRule);
//                if (!result.getResult().equals("T")) {
//                    throw new BusinessException("执行失败！");
//                }
//            }else{
//                log.info("【已到结束节点】流程结束！！");
//            }
//        }else{
//            log.info("【查找到无下级审核任务】流程结束！！");
//        }



        return param;
    }

    public Object afterInvoke(Map<String, Object> param) {

        // TODO Auto-generated method stub
        return null;
    }

    /**
     * 规则校验入口（专门给系统公式规则提供的）
     *
     * @param paramsVo
     */
    public void run(ParamsVo paramsVo) {
        beforeInvoke(paramsVo.getParams());
    }

    /**
     * description:
     *
     * @param iusProxyManager
     * @param auditsId
     * @return DataMap
     */
    private DataMap getAuditByAuditsId(ProxyManager iusProxyManager, String auditsId) {
        ParamsVo auditVo = new ParamsVo();
        auditVo.setParams("doCode", "dymicSql");
        auditVo.setParams("sqlKeyId", "ByDymicSql");
        auditVo.setParams("resultType", "objInfo");
        auditVo.setParams("resultObjType", "obj");
        auditVo.setKey("iusTransaction");
        auditVo.setParams("modelTypes", "s_sysAudit");
        auditVo.setParams("sysAudit.w_auditsId", auditsId);
        ResultEntity auditResult = (ResultEntity) iusProxyManager.doInvoke(auditVo);
        return (DataMap) auditResult.getEntity();
    }


    /**
     * description:
     *
     * @param nextUser sysAuditRule的taskNo
     * @return DataMap
     */
    private DataMap getAuditRuleByTaskNo(ProxyManager iusProxyManager, String nextUser) {
        ParamsVo params = new ParamsVo();
        params.setParams("doCode", "dymicSql");
        params.setParams("sqlKeyId", "ByDymicSql");
        params.setParams("resultType", "objInfo");
        params.setParams("resultObjType", "obj");
        params.setKey("iusTransaction");
        //通过下一审核节点查询规则
        params.setParams("modelTypes", "s_sysAuditRule");
        params.setParams("sysAuditRule.w_taskNo", nextUser);
        ResultEntity dymicSqlParamResult = (ResultEntity) iusProxyManager.doInvoke(params);
        return (DataMap) dymicSqlParamResult.getEntity();

    }

//    private ResultEntity insertAudit(ProxyManager iusProxyManager, DataMap sysAuditRule) {
//        ParamsVo paramVo = new ParamsVo();
//        paramVo.setParams("doCode", "dymicSql");
//        paramVo.setKey("iusTransaction");
//        paramVo.setParams("sqlKeyId", "ByDymicSql");
//        paramVo.setParams("resultType", "processSql");
//        paramVo.setParams("modelTypes", "i_sysAudit");
//        paramVo.setParams("sysAudit.auditType", sysAuditRule.get("auditType"));
//        paramVo.setParams("sysAudit.proId", sysAuditRule.get("proId"));
//        paramVo.setParams("sysAudit.auditsStatus", "10");
//        paramVo.setParams("sysAudit.checkUser", sysAuditRule.get("checkUser"));
//        paramVo.setParams("sysAudit.nextUser", sysAuditRule.get("next"));
//        paramVo.setParams("sysAudit.lastUser", sysAuditRule.get("last"));
//        paramVo.setParams("sysAudit.toUrl", sysAuditRule.get("toUrl"));
//        paramVo.setParams("sysAudit.num", sysAuditRule.get("num"));
//        paramVo.setParams("sysAudit.sysName", sysAuditRule.get("sysName"));
//        paramVo.setParams("sysAudit.pageName", sysAuditRule.get("pageName"));
//        paramVo.setParams("sysAudit.formName", sysAuditRule.get("formName"));
//
//        String proName = String.valueOf(sysAuditRule.get("proName"));
//        String taskName = String.valueOf(sysAuditRule.get("taskName"));
//        paramVo.setParams("sysAudit.proName", proName);
//        paramVo.setParams("sysAudit.taskName", taskName.split("-")[1]);
//        paramVo.setParams("sysAudit.taskNo", sysAuditRule.get("taskNo"));
//        paramVo.setParams("sysAudit.colName", sysAuditRule.get("colName"));
//        paramVo.setParams("sysAudit.tableName", sysAuditRule.get("tableName"));
//        paramVo.setParams("sysAudit.createTime", DateUtils.Now.fmt_yyyyMMdd_HHmmss());
//
//        paramVo.setParams("sysAudit.colNameY", sysAuditRule.get("colNameY"));
//        paramVo.setParams("sysAudit.colNameN", sysAuditRule.get("colNameN"));
//        paramVo.setParams("sysAudit.ifCustom", sysAuditRule.get("ifCustom"));
//        paramVo.setParams("sysAudit.linkUrl", sysAuditRule.get("linkUrl"));
//        return (ResultEntity) iusProxyManager.doInvoke(paramVo);
//    }

//    private ResultEntity insertAudit(DataMap sysAuditRule) {
//        //换成跨数据源的写法
//        String saveObjName = "i_sysAudit";
//        Map<String, Object> paramVo = new HashMap<String, Object>();
//        paramVo.put("sysAudit.auditType", sysAuditRule.get("auditType"));
//        paramVo.put("sysAudit.proId", sysAuditRule.get("proId"));
//        paramVo.put("sysAudit.auditsStatus", "10");
//        paramVo.put("sysAudit.checkUser", sysAuditRule.get("checkUser"));
//        paramVo.put("sysAudit.nextUser", sysAuditRule.get("next"));
//        paramVo.put("sysAudit.lastUser", sysAuditRule.get("last"));
//        paramVo.put("sysAudit.toUrl", sysAuditRule.get("toUrl"));
//        paramVo.put("sysAudit.num", sysAuditRule.get("num"));
//        paramVo.put("sysAudit.sysName", sysAuditRule.get("sysName"));
//        paramVo.put("sysAudit.pageName", sysAuditRule.get("pageName"));
//        paramVo.put("sysAudit.formName", sysAuditRule.get("formName"));
//        String proName = String.valueOf(sysAuditRule.get("proName"));
//        String taskName = String.valueOf(sysAuditRule.get("taskName"));
//        paramVo.put("sysAudit.proName", proName);
//        paramVo.put("sysAudit.taskName", (taskName.indexOf("-")>-1)?taskName.split("-")[1]:taskName);
//        paramVo.put("sysAudit.taskNo", sysAuditRule.get("taskNo"));
//        paramVo.put("sysAudit.colName", sysAuditRule.get("colName"));
//        paramVo.put("sysAudit.tableName", sysAuditRule.get("tableName"));
//        paramVo.put("sysAudit.createTime", DateUtils.Now.fmt_yyyyMMdd_HHmmss());
//        paramVo.put("sysAudit.colNameY", sysAuditRule.get("colNameY"));
//        paramVo.put("sysAudit.colNameN", sysAuditRule.get("colNameN"));
//        paramVo.put("sysAudit.ifCustom", sysAuditRule.get("ifCustom"));
//        paramVo.put("sysAudit.linkUrl", sysAuditRule.get("linkUrl"));
//        ResultEntity result = IusPluginUtil.getInstance().saveInvoke("plateform",saveObjName,paramVo);
//        log.info("【初始化下级审核任务结果】 - > taskName="+taskName+",proName="+proName+",result="+ JSONObject.fromObject(result));
//        return result;
//    }


//    private ResultEntity updateAudit(ProxyManager iusProxyManager, String auditsId,
//            String auditsStatus, String auditOpinion, Map<String, Object> param) {
//        ParamsVo upParamVo = new ParamsVo();
//        upParamVo.setParams("doCode", "dymicSql");
//        upParamVo.setKey("iusTransaction");
//        upParamVo.setParams("sqlKeyId", "ByDymicSql");
//        upParamVo.setParams("resultType", "processSql");
//        upParamVo.setParams("modelTypes", "u_sysAudit");
//        upParamVo.setParams("sysAudit.w_auditsId", auditsId);
//        upParamVo.setParams("sysAudit.auditsStatus", auditsStatus);
//        upParamVo.setParams("sysAudit.auditOpinion", auditOpinion);
//        upParamVo.setParams("sysAudit.modifyTime", DateUtils.Now.fmt_yyyyMMdd_HHmmss());
//        upParamVo.setParams("sysAudit.modifyUser", param.get("sysAudit.modifyUser"));
//        return (ResultEntity) iusProxyManager.doInvoke(upParamVo);
//    }


    private ResultEntity updateAudit(String auditsId,
                                     String auditsStatus, String auditOpinion, Map<String, Object> param) {
        //换成跨数据源的写法
        String saveObjName = "u_sysAudit";
        Map<String, Object> upParamVo = new HashMap<String, Object>();
        upParamVo.put("sysAudit.w_auditsId", auditsId);
        upParamVo.put("sysAudit.auditsStatus", auditsStatus);
        upParamVo.put("sysAudit.auditOpinion", auditOpinion);
        upParamVo.put("sysAudit.modifyTime", DateUtils.Now.fmt_yyyyMMdd_HHmmss());
        upParamVo.put("sysAudit.modifyUser", param.get("sysAudit.modifyUser"));
        ResultEntity result = IusPluginUtil.getInstance().saveInvoke("plateform",saveObjName,upParamVo);
        return result;
    }


    private DataMap getNodeByCode(Map<String, Object> param,String nodeCode) {
        if(StrUtil.isNull(nodeCode)){
            return  null;
        }
        Map<String, Object> whereMap_next = new HashMap<String, Object>();
        whereMap_next.put("sysAuditRule.w_taskNo", nodeCode);
        ResultEntity nextCodeResult = (ResultEntity) IusPluginUtil.getInstance().select("plateform", "obj", "s_sysAuditRule", whereMap_next);
        DataMap nextNodeInfo = (DataMap) nextCodeResult.getEntity();
        String next_nodeType = String.valueOf(nextNodeInfo.get("nodeType"));
        if ("judge".equals(next_nodeType)) {
            //递归
            String nextNode = "";
            String nodeConfig = String.valueOf(nextNodeInfo.get("nodeConfig"));
            JSONObject jObject = JSONObject.fromObject(nodeConfig);
            JSONArray jsonArray = (JSONArray) jObject.get("nexts");
            if (jsonArray.size() > 0) {
                for (int i = 0; i < jsonArray.size(); i++) {
                    JSONObject job = jsonArray.getJSONObject(i);  // 遍历 jsonarray 数组，把每一个对象转成 json 对象
                    nodeCode = String.valueOf(job.get("code"));
                    String rule = String.valueOf(job.get("rule"));
                    if(Validator.isNotNull(rule)){
                        String arg1 = rule.split("==")[0];
                        String arg2 = rule.split("==")[1];
                        if (arg2.equals(param.get(arg1))) {
                            nextNode = String.valueOf(job.get("code"));
                            break;
                        }
                    }

                }
            }
            return getNodeByCode(param, nextNode);
        }
        return nextNodeInfo;
    }




    private void initAudit(DataMap taskMap){
        String saveObjName = "i_sysAudit";
        Map<String, Object> paramsMap = new HashMap<String, Object>();
        paramsMap.put("sysAudit.auditType",taskMap.get("auditType"));
        paramsMap.put("sysAudit.proId",DateUtils.getNow());
        paramsMap.put("sysAudit.auditsStatus", "10");
        paramsMap.put("sysAudit.checkUser", taskMap.get("checkUser"));
        paramsMap.put("sysAudit.nextUser", taskMap.get("next"));
        paramsMap.put("sysAudit.lastUser", taskMap.get("last"));
        paramsMap.put("sysAudit.toUrl", taskMap.get("toUrl"));
        paramsMap.put("sysAudit.createTime", DateUtils.Now.fmt_yyyyMMdd_HHmmss());
        paramsMap.put("sysAudit.num", taskMap.get("num"));
        paramsMap.put("sysAudit.colNameY", taskMap.get("colNameY"));
        paramsMap.put("sysAudit.colNameN", taskMap.get("colNameN"));
        paramsMap.put("sysAudit.linkUrl", taskMap.get("linkUrl"));
        paramsMap.put("sysAudit.ifCustom", taskMap.get("ifCustom"));
        paramsMap.put("sysAudit.sysName", taskMap.get("sysName"));
        paramsMap.put("sysAudit.pageName", taskMap.get("pageName"));
        paramsMap.put("sysAudit.formName", taskMap.get("formName"));


//            paramsMap.put("sysAudit.proName", name);
        paramsMap.put("sysAudit.taskName", taskMap.get("taskName"));
        paramsMap.put("sysAudit.taskNo", taskMap.get("taskNo"));
        paramsMap.put("sysAudit.colName", taskMap.get("colName"));
        paramsMap.put("sysAudit.tableName", taskMap.get("tableName"));

        ResultEntity result = IusPluginUtil.getInstance().saveInvoke("plateform",saveObjName,paramsMap);
//            log.info("【初始化第一级审核任务结果】 - > taskName="+taskName+",proName="+name+",result="+ JSONObject.fromObject(result));

        if (!result.getResult().equals("T")) {
            throw new BusinessException("执行失败！");
        }

    }


}
